/******************************************************************************
 * Title:     Younker Web Appliaction Framework
 * Copyright: Copyright (c) 2004
 * Company:   YounkerSoft
 * Author: 	  Xiao Jian
 * Version:   2.0
 *****************************************************************************/
package com.younker.waf.html;

import java.sql.SQLException;
import java.util.List;

import javax.servlet.jsp.JspException;
import javax.servlet.jsp.tagext.TagSupport;

import org.apache.commons.dbutils.*;
import org.apache.commons.dbutils.handlers.ArrayListHandler;
import org.apache.commons.logging.*;

import com.younker.waf.db.DataSourceProvider;
/**
 * Tag for creating multiple &lt;select&gt; options from a ResultSet.  
 * 
 * <b>NOTE</b> - This tag requires a Java2 (JDK 1.2 or later) platform.
 *  @see org.apache.struts.taglib.html.optionsCollectionTag
 */

public class OptionsTag extends TagSupport {

    private static final Log log = LogFactory.getLog(OptionsTag.class);

    /**
     * SQL query string 
     */
    private String sql;

    /**
     * The style associated with this tag.
     */
    private String style = null;
    /**
     * The named style class associated with this tag.
     */
    private String styleClass = null;

    public String getStyle() {
        return style;
    }

    public void setStyle(String style) {
        this.style = style;
    }

    public String getStyleClass() {
        return styleClass;
    }

    public void setStyleClass(String styleClass) {
        this.styleClass = styleClass;
    }
    
    public String getSql() {
    	return OptionsConfig.getString(sql);
    }

    public void setSql(String string) {
        sql = string;
    }
    /**
     * Process the start of this tag.
     *
     * @exception JspException if a JSP exception has occurred
     */

    public int doStartTag() throws JspException {
        return SKIP_BODY;
    }

    /**
     * Process the end of this tag.
     *
     * @exception JspException if a JSP exception has occurred
     */
    public int doEndTag() throws JspException {

        // Acquire the select tag we are associated with
        SelectTag selectTag =
            (SelectTag) pageContext.getAttribute(SelectTag.SELECT_KEY);
        if (selectTag == null) {

        }
        StringBuffer sb = new StringBuffer();
        //query the database 
        QueryRunner run =
            new QueryRunner(DataSourceProvider.instance().getDataSource());
        ResultSetHandler h = new ArrayListHandler();
        List rs = null;
        try {
            rs = (List) run.query(getSql(), h);
        } catch (SQLException ex) {
            log.error("Generating option error ", ex); 
        }

        if (rs != null) {
            addOption(sb,"","",false); 
            for (int i = 0; i < rs.size(); i++) {
                Object[] row = (Object[]) rs.get(i);
                String label, value;
                if (row.length == 1) {
                    value = String.valueOf(row[0]);
                    label = String.valueOf(row[0]);
                } else if (row.length > 1) {
                    value = String.valueOf(row[0]);
                    label = String.valueOf(row[1]);
                } else {
                    label = ""; 
                    value = ""; 
                }
                addOption(sb, value, label, selectTag.isMatched(value));
            }
        }
        // Render this element to our writer
        ResponseUtils.write(pageContext, sb.toString());
        // Evaluate the remainder of this page
        return EVAL_PAGE;
    }

    /**
     * Release any acquired resources.
     */
    public void release() {

        super.release();
        style = null;
        styleClass = null;
    }

    // ------------------------------------------------------ Protected Methods

    /**
     * Add an option element to the specified StringBuffer based on the
     * specified parameters.
     *<p>
     * Note that this tag specifically does not support the
     * <code>styleId</code> tag attribute, which causes the HTML
     * <code>id</code> attribute to be emitted.  This is because the HTML
     * specification states that all "id" attributes in a document have to be
     * unique.  This tag will likely generate more than one <code>option</code>
     * element element, but it cannot use the same <code>id</code> value.  It's
     * conceivable some sort of mechanism to supply an array of <code>id</code>
     * values could be devised, but that doesn't seem to be worth the trouble.
     *
     * @param sb StringBuffer accumulating our results
     * @param value Value to be returned to the server for this option
     * @param label Value to be shown to the user for this option
     * @param matched Should this value be marked as selected?
     */
    protected void addOption(
        StringBuffer sb,
        String value,
        String label,
        boolean matched) {

        sb.append("<option value=\""); 
        sb.append(value);
        sb.append("\""); 
        if (matched) {
            sb.append(" selected=\"selected\""); 
        }
        if (style != null) {
            sb.append(" style=\""); 
            sb.append(style);
            sb.append("\""); 
        }
        if (styleClass != null) {
            sb.append(" class=\""); 
            sb.append(styleClass);
            sb.append("\""); 
        }
        sb.append(">"); 
        sb.append(label);
        sb.append("</option>\r\n"); 
    }

}
